/**
 * 
 */
package nus.mtech.presentation;

import java.awt.Dimension;
import java.awt.Font;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
import java.util.ArrayList;
import java.util.Date;

import javax.swing.JButton;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.SwingConstants;
import javax.swing.border.EtchedBorder;

import nus.mtech.ApplicationFacade;
import nus.mtech.constant.PresentationConstant;
import nus.mtech.subscription.ExtraFeature;
import nus.mtech.subscription.ExtraFeature.ExtraFeatureType;
import nus.mtech.subscription.MobileVoice;
import nus.mtech.subscription.Subscription;
import nus.mtech.util.DateUtil;
import nus.mtech.util.IntegerTextField;
import nus.mtech.util.StringUtil;

/**
 * @author Alvin Lee, Jiang Hao Min
 * 
 */
final class MobilePanel extends JPanel implements ActionListener {
	private static final long serialVersionUID = -5607390209585241584L;
	
	private static volatile MobilePanel INSTANCE;
	private JButton btnClear;
	private JButton btnUpdate;
	private JButton btnSearch;
	private JButton btnTransfer;
	private JComboBox comboBoxStatus;
	private JComboBox comboBoxOptionsStatus;
	private JComboBox comboBoxOptions;
	private JTextField txtAccountNo;
	private JTextField txtStartDate;
	private JTextField txtEndDate;
	private JTextField txtOptionStartDate;
	private JTextField txtOptionEndDate;
	private JTextField txtMobileVoiceNo;

	MobilePanel() {
		super(null);
		this.setBackground(PresentationConstant.CONSOLE_BACKGROUND);
		this.setPreferredSize(new Dimension(1004, 643));
		initialization();

	}

	public void initialization() {
		removeAll();

		final JLabel mobilePanelLabel = new JLabel();
		mobilePanelLabel.setHorizontalAlignment(SwingConstants.CENTER);
		mobilePanelLabel.setFont(new Font("", Font.BOLD, 16));
		mobilePanelLabel.setText("Mobile Voice");
		mobilePanelLabel.setBounds(0, 10, 1004, 21);
		add(mobilePanelLabel);

		JLabel lblAccountNo = new JLabel("Account No:");
		lblAccountNo.setBounds(90, 133, 106, 14);
		add(lblAccountNo);

		btnClear = new JButton("Clear");
		btnClear.setBounds(275, 316, 89, 23);
		btnClear.addActionListener(this);
		add(btnClear);

		JLabel lblMobileVoice = new JLabel("Mobile Voice Subscriptions");
		lblMobileVoice.setFont(new Font("Dialog", Font.BOLD, 14));
		lblMobileVoice.setBounds(90, 88, 242, 21);
		add(lblMobileVoice);

		JLabel lbTelephoneNo = new JLabel("Mobile Voice No:");
		lbTelephoneNo.setBounds(90, 170, 106, 14);
		add(lbTelephoneNo);

		JLabel lblStartDate = new JLabel("Date Commenced:");
		lblStartDate.setBounds(90, 201, 106, 14);
		add(lblStartDate);

		JLabel lblStatus = new JLabel("Status:");
		lblStatus.setBounds(90, 270, 106, 14);
		add(lblStatus);

		comboBoxStatus = new JComboBox();
		comboBoxStatus.setBounds(206, 267, 137, 20);
		comboBoxStatus.addItem("");
		comboBoxStatus.addItem("Active");
		comboBoxStatus.addItem("Terminate");
		add(comboBoxStatus);

		btnUpdate = new JButton("Update / Add");
		btnUpdate.setBounds(125, 316, 106, 23);
		btnUpdate.addActionListener(this);
		add(btnUpdate);
		
		btnSearch = new JButton("Search");
		btnSearch.setBounds(502, 129, 89, 23);
		btnSearch.addActionListener(this);
		add(btnSearch);
		
		txtAccountNo = new JTextField();
		txtAccountNo.setColumns(10);
		txtAccountNo.setBounds(206, 130, 248, 20);
		add(txtAccountNo);
		
		txtMobileVoiceNo = new IntegerTextField();
		txtMobileVoiceNo.setColumns(10);
		txtMobileVoiceNo.setBounds(206, 167, 248, 20);
		add(txtMobileVoiceNo);
		
		JLabel lblBorder = new JLabel();
		lblBorder.setBorder(new EtchedBorder(EtchedBorder.LOWERED));
		lblBorder.setBounds(40, 71, 944, 290);
		add(lblBorder);
		
		txtStartDate = new JTextField();
		txtStartDate.setEditable(false);
		txtStartDate.setColumns(10);
		txtStartDate.setBounds(206, 198, 248, 20);
		add(txtStartDate);
		
		JLabel lblEndDate = new JLabel("Date Terminated:");
		lblEndDate.setBounds(90, 235, 106, 14);
		add(lblEndDate);
		
		txtEndDate = new JTextField();
		txtEndDate.setEditable(false);
		txtEndDate.setColumns(10);
		txtEndDate.setBounds(206, 232, 248, 20);
		add(txtEndDate);
		
		comboBoxOptionsStatus = new JComboBox();
		comboBoxOptionsStatus.setEnabled(false);
		comboBoxOptionsStatus.setBounds(206, 463, 137, 20);
		comboBoxOptionsStatus.addItem("Not Registered");
		comboBoxOptionsStatus.addItem("Active");
		comboBoxOptionsStatus.addItem("Terminate");
		add(comboBoxOptionsStatus);
		
		JLabel lblOptions = new JLabel("Options:");
		lblOptions.setBounds(90, 430, 106, 14);
		add(lblOptions);
		
		JLabel lblCallTransferBorder = new JLabel();
		lblCallTransferBorder.setBounds(40, 381, 944, 227);
		lblCallTransferBorder.setBorder(new EtchedBorder(EtchedBorder.LOWERED));
		add(lblCallTransferBorder);
		
		JLabel lblExtraOptions = new JLabel("Extra Options");
		lblExtraOptions.setFont(new Font("Dialog", Font.BOLD, 14));
		lblExtraOptions.setBounds(90, 398, 242, 21);
		add(lblExtraOptions);
		
		JLabel lblStartDate2 = new JLabel("Date Commenced:");
		lblStartDate2.setBounds(90, 501, 106, 14);
		add(lblStartDate2);
		
		JLabel lblEndDate2 = new JLabel("Date Terminated:");
		lblEndDate2.setBounds(90, 536, 106, 14);
		add(lblEndDate2);
		
		txtOptionStartDate = new JTextField();
		txtOptionStartDate.setEditable(false);
		txtOptionStartDate.setColumns(10);
		txtOptionStartDate.setBounds(206, 498, 248, 20);
		add(txtOptionStartDate);
		
		txtOptionEndDate = new JTextField();
		txtOptionEndDate.setEditable(false);
		txtOptionEndDate.setColumns(10);
		txtOptionEndDate.setBounds(206, 533, 248, 20);
		add(txtOptionEndDate);
		
		btnTransfer = new JButton("Update");
		btnTransfer.setEnabled(false);
		btnTransfer.setBounds(125, 572, 106, 23);
		btnTransfer.addActionListener(this);
		add(btnTransfer);
		
		JLabel lblOptionStatus = new JLabel("Status:");
		lblOptionStatus.setBounds(90, 466, 106, 14);
		add(lblOptionStatus);
		
		comboBoxOptions = new JComboBox();
		comboBoxOptions.setEnabled(false);
		comboBoxOptions.setBounds(206, 427, 137, 20);
		comboBoxOptions.addItem("Please Select");
		comboBoxOptions.addItem("Data Service");
		comboBoxOptions.addItem("Roaming Calls");
		add(comboBoxOptions);
		
		comboBoxOptions.addItemListener(new ItemListener(){
			public void itemStateChanged(ItemEvent itemEvent) {
				popupExtraOptions();
			}
		});
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * java.awt.event.ActionListener#actionPerformed(java.awt.event.ActionEvent)
	 */
	public void actionPerformed(ActionEvent ae) {
		if (ae.getSource() == btnClear) {
			clear();			
		} else if (ae.getSource() == btnSearch) {
//			enableEditMode(true);
			if (StringUtil.isBlank(txtAccountNo.getText())) {
				JOptionPane.showMessageDialog(this, "Account No Required.", "Please enter Account No", JOptionPane.ERROR_MESSAGE);
			}else{
				String accountNo = txtAccountNo.getText().trim().toUpperCase();
				ArrayList<Subscription> subscriptionList = ApplicationFacade.getInstance().getSubscription(accountNo);
				if(null != subscriptionList){
					MobileVoice mobileVoice = null;
					for(Subscription sub: subscriptionList){
						if(sub instanceof MobileVoice){
							mobileVoice = (MobileVoice)sub;
							break;
						}
					}
					
					if(null != mobileVoice){
						clear();
						
						txtAccountNo.setText(accountNo);
						txtMobileVoiceNo.setText(String.valueOf(mobileVoice.getTelephoneNo()));
						if(null != mobileVoice.getStartDate()){
							txtStartDate.setText(DateUtil.formatDate(mobileVoice.getStartDate(), DateUtil.DATE_TIME_FORMAT));
						}
						if(null != mobileVoice.getEndDate()){
							txtEndDate.setText(DateUtil.formatDate(mobileVoice.getEndDate(), DateUtil.DATE_TIME_FORMAT));
						}
						if(mobileVoice.getStatus()){
							comboBoxStatus.setSelectedIndex(1);
						}else{
							comboBoxStatus.setSelectedIndex(2);
						}

						btnSearch.setEnabled(false);
						txtAccountNo.setEditable(false);
						btnTransfer.setEnabled(true);
						comboBoxOptions.setEnabled(true);
						comboBoxOptionsStatus.setEnabled(true);
					}
					else {
						JOptionPane.showMessageDialog(this, "No existing Mobile Voice Subscription", "No subscription", 
								JOptionPane.ERROR_MESSAGE);
					}
				}
				else {
					JOptionPane.showMessageDialog(this, "No existing Mobile Voice Subscription", "No subscription", 
							JOptionPane.ERROR_MESSAGE);
				}
			}
		}else if (ae.getSource() == btnUpdate) {
			String errMsg = "";
			if(StringUtil.isBlank(txtAccountNo.getText())){
				errMsg += "Account No is required.\n";
			}else if(null == ApplicationFacade.getInstance().getCustomerByAccountNo(txtAccountNo.getText())){
				errMsg += "Account No cannot be found.\n";
			}
			
			if(StringUtil.isBlank(txtMobileVoiceNo.getText())){
				errMsg += "Mobile Voice No is required.\n";
			}else if(!StringUtil.isNumeric(txtMobileVoiceNo.getText())){
				errMsg += "Mobile Voice No must be numeric.\n";
			}
			
			if(StringUtil.isNotEmpty(errMsg)){
				JOptionPane.showMessageDialog(this, errMsg,	"Error Message", JOptionPane.ERROR_MESSAGE);
			}else{
				boolean isNew = true;
				String accountNo = txtAccountNo.getText().trim().toUpperCase();
				MobileVoice mobileVoice = getMobileVoiceByAccountNo(accountNo);
				
				if(null == mobileVoice){
					mobileVoice = new MobileVoice(new Date(), null, true);
					mobileVoice.setTelephoneNo(Long.parseLong(txtMobileVoiceNo.getText()));
					ApplicationFacade.getInstance().addSubscription(accountNo, mobileVoice);
				}else{
					isNew = false;
					
					mobileVoice.setTelephoneNo(Long.parseLong(txtMobileVoiceNo.getText()));
					if(comboBoxStatus.getSelectedIndex() == 2){
						mobileVoice.setStatus(false);
						mobileVoice.setEndDate(new Date());
					}else{
						mobileVoice.setStatus(true);
						mobileVoice.setEndDate(null);
					}
				}
				
				txtMobileVoiceNo.setText(String.valueOf(mobileVoice.getTelephoneNo()));
				if(null != mobileVoice.getStartDate()){
					txtStartDate.setText(DateUtil.formatDate(mobileVoice.getStartDate(), DateUtil.DATE_TIME_FORMAT));
				}
				if(null != mobileVoice.getEndDate()){
					txtEndDate.setText(DateUtil.formatDate(mobileVoice.getEndDate(), DateUtil.DATE_TIME_FORMAT));
				}else{
					txtEndDate.setText("");
				}
				if(mobileVoice.getStatus()){
					comboBoxStatus.setSelectedIndex(1);
				}else{
					comboBoxStatus.setSelectedIndex(2);
				}
				
				if(isNew){
					btnTransfer.setEnabled(true);
					comboBoxOptions.setEnabled(true);
					comboBoxOptionsStatus.setEnabled(true);
					
					JOptionPane.showMessageDialog(this, "Mobile Voice Subscription is created successfully.",
						"Successful Message",
						JOptionPane.INFORMATION_MESSAGE);
				}else{
					JOptionPane.showMessageDialog(this, "Mobile Voice Subscription is updated successfully.",
							"Successful Message",
							JOptionPane.INFORMATION_MESSAGE);
				}
			}
		}else if(ae.getSource() == btnTransfer){
			String errMsg = "";
			
			if(StringUtil.isBlank(txtAccountNo.getText())){
				errMsg += "Account No is required.\n";
			}else if(null == ApplicationFacade.getInstance().getCustomerByAccountNo(txtAccountNo.getText())){
				errMsg += "Account No cannot be found.\n";
			}
			
			int optionIndex = comboBoxOptions.getSelectedIndex();
			if(optionIndex == 0){
				errMsg += "Option is required.\n";
			}
			
			if(StringUtil.isNotEmpty(errMsg)){
				JOptionPane.showMessageDialog(this, errMsg,	"Error Message", JOptionPane.ERROR_MESSAGE);
			}else{
				String accountNo = txtAccountNo.getText().trim();
				MobileVoice mobileVoice = getMobileVoiceByAccountNo(accountNo);
				
				boolean isNew = true;
				ExtraFeatureType extraFeatureType = null;
				if(optionIndex == 1){
					extraFeatureType = ExtraFeatureType.DataService;
				}else if(optionIndex == 2){
					extraFeatureType = ExtraFeatureType.Roaming;
				}
				
				ExtraFeature extraFeature = null;
				if(mobileVoice.getMapOfExtraFeatures().containsKey(extraFeatureType)){
					extraFeature = mobileVoice.getMapOfExtraFeatures().get(extraFeatureType);
					isNew = false;
					
					if(comboBoxOptionsStatus.getSelectedIndex() == 2){
						extraFeature.setActiveStatus(false);
						extraFeature.setEndDate(new Date());
					}else{
						extraFeature.setActiveStatus(true);
						extraFeature.setEndDate(null);
					}
				}else{
					ApplicationFacade.getInstance().addExtraFeature(extraFeatureType, new Date(), null, true, mobileVoice);
					extraFeature = mobileVoice.getMapOfExtraFeatures().get(extraFeatureType);
				}
				
				if(extraFeature.isActiveStatus()){
					comboBoxOptionsStatus.setSelectedIndex(1);
				}else{
					comboBoxOptionsStatus.setSelectedIndex(2);
				}
				if(null != extraFeature.getStartDate()){
					txtOptionStartDate.setText(DateUtil.formatDate(extraFeature.getStartDate(), DateUtil.DATE_TIME_FORMAT));
				}
				if(null != extraFeature.getEndDate()){
					txtOptionEndDate.setText(DateUtil.formatDate(extraFeature.getEndDate(), DateUtil.DATE_TIME_FORMAT));
				}else{
					txtOptionEndDate.setText("");
				}
				
				if(isNew){
					JOptionPane.showMessageDialog(this, "Extra Option is created successfully.",
						"Successful Message",
						JOptionPane.INFORMATION_MESSAGE);
				}else{
					JOptionPane.showMessageDialog(this, "Extra Option is updated successfully.",
							"Successful Message",
							JOptionPane.INFORMATION_MESSAGE);
				}
			}
		}
	}
	
	private void popupExtraOptions(){
		if(comboBoxOptions.getSelectedIndex() > 0){
			String accountNo = txtAccountNo.getText().trim();
			MobileVoice mobileVoice = getMobileVoiceByAccountNo(accountNo);
			
			if(null != mobileVoice){
				int optionIndex = comboBoxOptions.getSelectedIndex();
				ExtraFeatureType extraFeatureType = null;
				if(optionIndex == 1){
					extraFeatureType = ExtraFeatureType.DataService;
				}else if(optionIndex == 2){
					extraFeatureType = ExtraFeatureType.Roaming;
				}
				
				ExtraFeature extraFeature = mobileVoice.getMapOfExtraFeatures().get(extraFeatureType);
				if(null != extraFeature){
					if(extraFeature.isActiveStatus()){
						comboBoxOptionsStatus.setSelectedIndex(1);
					}else{
						comboBoxOptionsStatus.setSelectedIndex(2);
					}
					
					if(null != extraFeature.getStartDate()){
						txtOptionStartDate.setText(DateUtil.formatDate(extraFeature.getStartDate(), DateUtil.DATE_TIME_FORMAT));
					}else{
						txtOptionStartDate.setText("");
					}
					
					if(null != extraFeature.getEndDate()){
						txtOptionEndDate.setText(DateUtil.formatDate(extraFeature.getEndDate(), DateUtil.DATE_TIME_FORMAT));
					}else{
						txtOptionEndDate.setText("");
					}
				}else{
					comboBoxOptionsStatus.setSelectedIndex(0);
					txtOptionStartDate.setText("");
					txtOptionEndDate.setText("");
				}
			}
		}else{
			comboBoxOptionsStatus.setSelectedIndex(0);
			txtOptionStartDate.setText("");
			txtOptionEndDate.setText("");
		}
	}
	
	private MobileVoice getMobileVoiceByAccountNo(String accountNo){
		MobileVoice mobileVoice = null;
		
		ArrayList<Subscription> subscriptionList = ApplicationFacade.getInstance().getSubscription(accountNo);
		if(null != subscriptionList){
			for(Subscription sub: subscriptionList){
				if(sub instanceof MobileVoice){
					mobileVoice = (MobileVoice)sub;
					break;
				}
			}
		}
		
		return mobileVoice;
	}
	
	public void clear() {
		btnSearch.setEnabled(true);
		txtAccountNo.setEditable(true);
		btnTransfer.setEnabled(false);
		comboBoxOptions.setEnabled(false);
		comboBoxOptionsStatus.setEnabled(false);
		
		comboBoxStatus.setSelectedIndex(0);
		comboBoxOptionsStatus.setSelectedIndex(0);
		comboBoxOptions.setSelectedIndex(0);
		txtAccountNo.setText("");
		txtMobileVoiceNo.setText("");
		txtStartDate.setText("");
		txtEndDate.setText("");
		txtOptionStartDate.setText("");
		txtOptionEndDate.setText("");
		
//		enableEditMode(false);
	}
	
	@SuppressWarnings("unused")
	private void enableEditMode(boolean b) {
		btnSearch.setEnabled(!b);
		txtAccountNo.setEditable(!b);
		comboBoxOptions.setEnabled(b);
		comboBoxOptionsStatus.setEnabled(b);
		txtOptionStartDate.setEnabled(b);
		txtOptionEndDate.setEnabled(b);
		btnTransfer.setEnabled(b);
		btnUpdate.setEnabled(b);
	}
	
	public static MobilePanel getInstance() {
		synchronized (MobilePanel.class) {
			if (INSTANCE == null) {
				INSTANCE = new MobilePanel();
			}
			return INSTANCE;
		}
	}
}
